﻿using System;
using System.IO;
using System.Net;
using System.Text;
using System.Web.Script.Serialization;
using Microsoft.Build.Framework;
using Microsoft.Build.Utilities;

namespace Chatu.MsbuildTasks
{
    public class WebServerManagementTask : Task
    {
        [Required]
        public string ServiceUri { get; set; }

        [Required]
        public string AccessKey { get; set; }

        [Required]
        public string MethodName { get; set; }

        [Required, Output]
        public string SiteName { get; set; }

        public override bool Execute()
        {
            try
            {
                string methodName = string.Empty;

                switch (MethodName.ToLower())
                {
                    case "startwebsite":
                        methodName = "StartWebSite";
                        break;
                    case "stopwebsite":
                        methodName = "StopWebSite";
                        break;
                    default:
                        throw new Exception("Invalid MethodName. Options[StartWebSite, StopWebSite].");
                }

                Log.LogMessage("Processing [{0}]:[{1}]", methodName, SiteName);
                ProcessRequest(methodName, "siteName", SiteName);
            }
            catch(Exception ex)
            {
                Log.LogErrorFromException(ex);
                return false;
            }

            return true;
        }

        #region Private Helpers

        private JavaScriptSerializer _serializer;

        private JavaScriptSerializer Serializer
        {
            get
            {
                if (_serializer == null)
                    return _serializer = new JavaScriptSerializer();

                return _serializer;
            }
        }

        private string ProcessRequest(string methodName, string varName, object postData)
        {
            string uri = ServiceUri;
            string accessKey = AccessKey;
            string url = string.Format("{0}?m={1}", uri, methodName);

            string data = "{}";

            if (postData != null)
            {
                data = string.Format("{0}\"{2}\":{3}{1}", "{", "}", varName, Serializer.Serialize(postData));
            }

            byte[] byteArray = Encoding.UTF8.GetBytes(data);

            HttpWebRequest request = (HttpWebRequest)WebRequest.Create(url);
            string toReturn;
            bool isError;

            request.Method = "POST";
            request.ContentType = "application/json; charset=utf-8";
            request.ContentLength = byteArray.Length;
            request.Headers["accessKey"] = accessKey;

            using (Stream dataStream = request.GetRequestStream())
            {
                dataStream.Write(byteArray, 0, byteArray.Length);
            }

            using (HttpWebResponse response = (HttpWebResponse)request.GetResponse())
            {
                using (StreamReader reader = new StreamReader(response.GetResponseStream()))
                {
                    isError = (response.Headers["jsonerror"] != null);
                    toReturn = reader.ReadToEnd();
                }
            }

            if (isError)
            {
                throw new Exception(Serializer.Deserialize<ServiceMessage>(toReturn).Message);
            }

            return toReturn;
        }

        private class ServiceMessage
        {
            public string Message { get; set; }
            public string Success { get; set; }
        }

        #endregion
    }
}
